{
 "cells": [
  {
   "cell_type": "markdown",
   "id": "891a27e5-f633-4d9b-9de2-f25c104e5723",
   "metadata": {},
   "source": [
    "# 本人自述\n",
    "\n",
    "1. 代码非本专业，因兴趣自学。以本文爬取的内容激励自己坚持学习，不断获取更多资源。数年间断断续续，至今仍在入门阶段，只会一些简单的爬虫。下面的目标是学会WEB逆向，获取付费论坛中的资源。但现在已非学生，不再有可以肆意挥霍的时间，未来能走到哪一步仍未可知。\n",
    "2. 本文简单梳理一下爬虫的逻辑，为的是再复习复习代码，毕竟间隔时间太长了，一年多以来只是小修小改。另外，也是第一次使用jupyter notebook，熟悉一下使用。"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 代码文件介绍\n",
    "\n",
    "1. Spider 文件夹内有三个文件夹，分别是：cili、data、Service。cili存放爬虫文件；data存放数据库文件；Service有三个`py`文件，分别是ips.py（早期用来获取网上的免费IP，早已废弃不用）、service.py（执行与数据库的相关操作）、ua.py（早期为配合ips.py实现伪装，虽然现在代码中还在用，但没了IP也无用，懒得删）。\n",
    "2. 着重介绍一下cili文件夹。里面有4个文件夹和一个`py`文件，分别是caoliu（爬草榴）、sehuatang（爬色花堂）、service、total（爬其他网站）、ciliProxy.py（启动caoliu和sehuatang）。因为所有的网站没能写到一个`py`文件中，所以有了service文件夹（注意和上面的Service文件夹区分），用来存放caoliu、sehuatang、total中重复的函数。\n",
    "3. 数据库字段（以total.db为例）：num为序号，tag为从title中提取的标签，title为资源名，url为该资源网页的网址，link不一定有值（如果获取资源磁力还需要打开别的网页，新网页网址即为link），magnet为资源磁力链接，size、duration、postdate不一定有值（分别为网页中写的该资源大小、时长和发布时间，recorddate为爬取时间，site为资源来自的网站名称，status为0或1（0为未下载，1为已下载）。"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 代码解释\n",
    "## cili\n",
    "### caoliu\n",
    "\n",
    "caoliu文件夹中有两个`py`文件：caoliu.py、create.py（其他文件一样，不再赘述）。create.py创建数据库文件，一开始运行一次即可，后面不再用到。caoliu.py即为爬取草榴网站的主要部分。下面看一下该文件："
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from sys import path as path2\n",
    "from time import sleep, strftime, localtime, gmtime\n",
    "from threading import Thread, active_count\n",
    "\n",
    "from bs4 import BeautifulSoup\n",
    "from rich import print as rprint\n",
    "\n",
    "path2.append('d:/Spider')\n",
    "from Service import service\n",
    "from service import req, title2tag"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "这是用到的库。`path2`是为了能够`import`Service中的service，不然无论是绝对引用还是相对引用，都会报错。`time`库的作用是多线程中暂时休眠和获取当前时间（记录爬取时间，会写入数据库中）。`rich`库可有可无，`rprint`函数的作用是在控制台打印彩色的文本。service中的req和title2tag的作用分别是进行网络请求和从title中提取标签（tag）。"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "主体为`Caoliu`类，我看这个的注释写的比较全，就不再说了"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### sehuatang\n",
    "\n",
    "代码结构和caoliu非常相似，也不说了。为什么这么相似还写成了两个文件？其实一开始只是爬一个网站，所以第一版的代码只适用于当前网站，后面发现更多的网站，就为每个网站写一个爬虫。逐渐发现代码非常相似，就把解析规则写到json文件里，代码合并成一个通用模板，从而诞生了total，剩下caoliu和sehuatang是因为它们都有不太一样的地方。或许可以合到一起去，但后面就懒得弄了。"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### service\n",
    "\n",
    "analyze.py, collect.py, get_fanhao.py, jingjian.py均为进行一些处理而写的，爬虫中没有用到，里面也有一些注释，此处不再解释。说一下get_fanhao.py，从文件名也可以看出来，该文件是为了收集番号的，因为我不喜欢看日本作品，所以搜集了一些番号，用来过滤掉一些资源，不记录到数据库。\n",
    "\n",
    "req.py是对各个网站进行网络请求的函数，`cloudscraper`只在函数`reqSehuatang`中用到，因为色花堂用到了免费的五秒盾好像，记不太清了。\n",
    "\n",
    "title2tag.py根据title对资源进行处理，包括提取标签、识别语言、过滤黑名单。\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### total\n",
    "\n",
    "这个算是内容最多的文件了，主要是一个`Numdomain`类，因为大部分网站的域名都是数字，所以起了这个名字。\n",
    "\n",
    "`prepare`和`savedb`函数抽取了`numdomain`和`gcbt`函数（对应着不同的网站）重复的部分，`prepare`函数是刚开始的部分，`savedb`是获取数据之后保存到数据库的部分。我看里面还有一些我调试的代码片段没有删，就这样吧。\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 结语\n",
    "\n",
    "就这样吧。\n",
    "我的初衷不是这样子的，但写着写着就偏航了。看起来很敷衍，但现在我好像就是想敷衍了事。\n",
    "\n",
    "说实话，这些网站上的东西质量很差，遍地都是水印。我现在对这些已经没有丝毫的兴趣了，但还是定期运行一下爬虫，尽管我知道我已经半年没看我爬的这些东西了。\n",
    "\n",
    "——2023.12.12"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3 (ipykernel)",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.10.6"
  },
  "widgets": {
   "application/vnd.jupyter.widget-state+json": {
    "state": {},
    "version_major": 2,
    "version_minor": 0
   }
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
